java对象hashCode存在的必要性是什么?

您所在的位置:网站首页 java hashcode是什么 java对象hashCode存在的必要性是什么?

java对象hashCode存在的必要性是什么?

2024-07-16 02:58| 来源: 网络整理| 查看: 265

加快判断两个对象是否相等

为什么是“加快”判断呢?接下来我们好好履履什么是hashCode,还有hashCode的作用场景,只要清晰的认识到hashCode的整个逻辑,什么八股“hashCode跟equals”这种问题再也不会难倒了。

1、hashCode是什么? 1.1、从源码看起 /** * Returns a hash code value for the object. This method is * supported for the benefit of hash tables such as those provided by * {@link java.util.HashMap}. *

* The general contract of {@code hashCode} is: * * Whenever it is invoked on the same object more than once during * an execution of a Java application, the {@code hashCode} method * must consistently return the same integer, provided no information * used in {@code equals} comparisons on the object is modified. * This integer need not remain consistent from one execution of an * application to another execution of the same application. * If two objects are equal according to the {@code equals(Object)} * method, then calling the {@code hashCode} method on each of * the two objects must produce the same integer result. * It is not required that if two objects are unequal * according to the {@link java.lang.Object#equals(java.lang.Object)} * method, then calling the {@code hashCode} method on each of the * two objects must produce distinct integer results. However, the * programmer should be aware that producing distinct integer results * for unequal objects may improve the performance of hash tables. * *

* As much as is reasonably practical, the hashCode method defined by * class {@code Object} does return distinct integers for distinct * objects. (This is typically implemented by converting the internal * address of the object into an integer, but this implementation * technique is not required by the * Java™ programming language.) * * @return a hash code value for this object. * @see java.lang.Object#equals(java.lang.Object) * @see java.lang.System#identityHashCode */ public native int hashCode();

我简单的翻译一下,主要有这么几个点:

返回一个对象的hash码,可以为hash表这样的hash数据结构提供便利在一个Java进程内,一个对象的hashCode 始终是相等的硬性要求,如果通过equals比较两个对象是否相等时,那么一定要保证相等的两个对象的hashCode也是相等的它不是必需的,如果按照equals(java.lang.Object)法两个对象是不平等的,然后调用hashCode方法每一个对象必须产生不同的整数结果。然而,程序员应该意识到,产生不同的整数结果的不平等的对象可能会提高哈希表的性能。这个hashCode是由内存地址计算得到的。

我们可以得到结论就是,判断两个对象是否相等在Java中根本跟hashCode没半毛线关系,用的是equals方法判断两个对象是否相等。但是有些对象equals会消耗比较多的性能,比如String对象需要对每个字符做比较,所以利用了hashCode先做一次预判断(O(1)),当hashCode相等的时候再使用equals再做判断。关于这个点,可以从我们熟悉的HashMap里面得到答案。每次判断key相等时候都会想比较hash(这个值是从hashCode计算出来的),然后再==,然后再equals。这个过程已经可以筛选掉一大波不击中的key了。

if (p.hash == hash && ((k = p.key) == key || (key != null && key.equals(k))))

为什么hashCode为什么就能确定两个对象不一样?这个方法是native的,在网上找了一张图,我们通过这张图,来了解到它的计算方式

1.2、hashCode的生成机制

参考:https://blog.caoxudong.info/blog/2013/12/12/default_hashcode_implmentation_in_hotspot

在这里插入图片描述 得到的结论就是:hashCode会被记录到对象头里面,生成方式是根据对象地址来做移位跟与操作得到的。所以就有了下面的问题,也是之前的一篇文章提到过的。

1.3、hashCode与==的关系

==:这个符号是判断两个对象的内存地址是否一致 hashCode:是通过内存地址计算出来的 所以,我们在不覆盖hashCode方法的情况下,可以姑且的认为等于一个内存地址的一个标志,但是毕竟是hash算法,肯定会存在hash冲突的情况,这里就不深究下去了。所以Java明确告诉你判断两个对象是否相等用的是equals方法,除了你自己,JVM也不知道这两个对象是否相等。

2、为什么要使用hashCode

看完了上述的描述之后,我们就可以得到答案了,就是回归点题的问题,它存在的必要性就是加速两个对象的判断过程。 还有其二,其二就是方便于hash表的使用,hash表可以根据这个hashCode去计算一个实用的hash码做hash处理。

3、如何正确的使用hashCode

正确使用hashCode码的方式无非就是老生长谈的equals跟hashCode的问题。那就是如果重写了equals的时候,一定要重写hashCode方法。一般来说可以自己根据业务逻辑设计一个hash算法,算出两个对象是否相等,而不仅仅使用内存地址。特别要注意的是在hashMap中去使用这个的时候。



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3